﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Threading.Tasks;
using Brc_PaaS.Common.Entity;
using Brc_PaaS.Common.Model.Apollo;
using Brc_PaaS.Common.Model.Basic;
using Brc_PaaS.Common.Model.Exceptionless;
using Brc_PaaS.Core.Apollo.Service;
using Brc_PaaS.Core.Exceptionless;
using Brc_PaaS.Dal;
using Exceptionless;
using Exceptionless.Logging;
using Microsoft.Extensions.Configuration;

namespace Brc_PaaS.Bll.Exceptionless
{
    public class ExceptionlessLog : IExceptionlessLog
    {

        private IRepository<Ass_Exceptionless> _exceptionless;
        private ILogManager _logManager;
        private LogModel _logConfig;
        private IApolloConfigService _apolloConfigService;
        private readonly IConfiguration _configuration;
        public ExceptionlessLog(IRepository<Ass_Exceptionless> exceptionless, ILogManager logManager, IConfiguration configuration,IApolloConfigService apolloConfigService)
        {
            _exceptionless = exceptionless;
            _logManager = logManager;
            _configuration = configuration;
            _apolloConfigService = apolloConfigService;
            _logConfig = _configuration.GetSection("Exceptionless").Get<LogModel>();
        }
        public BaseResponseModel CreateProject(Bas_System systemInfo, string accountId, string token)
        {
            BaseResponseModel result = new BaseResponseModel() { IsSuccess = false, Msg = string.Empty };
            var isExist = _exceptionless.Exist(i => i.SystemId == systemInfo.Id);
            if (isExist)
            {
                result.Msg = "该系统已经存在一个日志项目,不能再申请,如需帮助请联系管理员";
                return result;
            }
            EplCreateProjectReqModel model = new EplCreateProjectReqModel();
            _logConfig.Token = token;
            model.name = string.IsNullOrEmpty(systemInfo.Ch_Name) ? systemInfo.Name : systemInfo.Ch_Name;
            model.organization_id = _logConfig.Organization_Id;
            _logManager.LogConfig = _logConfig;
            //创建系统
            var createProjectResult = _logManager.CreateProjectInExceptionless(model);
            if (!createProjectResult.IsSuccess)
            {
                result.Msg = createProjectResult.Msg;
                Task.Run(() =>
                {
                    ExceptionlessClient.Default.CreateLog("Brc_PaaS.Bll.Exceptionless.ExceptionlessLog.CreateProject", $"业务系统：{model.name}(系统Id为【{systemInfo.Id}】)，于【{DateTime.Now.ToString("s")}】申请创建Exceptionless项目失败。失败原因：【{createProjectResult.Msg}】", LogLevel.Error).Submit();
                });
                return result;
            }
            EplCreateApiKeyReqModel apiKeyModel = new EplCreateApiKeyReqModel();
            apiKeyModel.notes = $"{systemInfo.Name}创建项目，创建时间:{DateTime.Now.ToString("s")}";
            apiKeyModel.organization_id = model.organization_id;
            apiKeyModel.project_id = createProjectResult.Data.id;
            //创建系统APIKEY
            var createApiKeyResult = _logManager.CreateApiKeyForBusinessSystemInExceptionless(apiKeyModel);
            if (!createApiKeyResult.IsSuccess)
            {
                Task.Run(() =>
                {
                    ExceptionlessClient.Default.CreateLog("Brc_PaaS.Bll.Exceptionless.ExceptionlessLog.CreateProject", $"业务系统：{model.name}(系统Id为【{systemInfo.Id}】)，于【{DateTime.Now.ToString("s")}】申请创建Exceptionless APIKEY失败。失败原因：【{createApiKeyResult.Msg}】", LogLevel.Error);
                });
            }
            Ass_Exceptionless ass_Exceptionless = new Ass_Exceptionless()
            {
                Id = Guid.NewGuid().ToString("N"),
                ProjectName = model.name,
                ProjectId = createProjectResult.Data.id,
                ProjectKey = createApiKeyResult.IsSuccess ? createApiKeyResult.Data.id : "",
                Status = 1,
                SystemId = systemInfo.Id,
                CreateTime = DateTime.Now,
                CreateUserId = accountId
            };

            //如果操作失败，应该删除Exceptionless中删除已经创建好的项目，此处暂时忽略该操作
            result.IsSuccess = _exceptionless.AddItem(ass_Exceptionless) > 0;
            result.Msg = result.IsSuccess ? "操作成功" : "操作失败";
            return result;


        }

        public ResponseModel<EplSearchExceptionDetailModel> GetEventDetail(string eventId,string token)
        {
            _logConfig.Token = token;
            _logManager.LogConfig = _logConfig;
            var result = _logManager.GetExceptionDetailFromExceptionless(eventId);
            return result;
        }

        public ResponseModel<List<EplSearchEventResModel>> QueryEvents(EplSearchEventReqModel model, out int total,string token)
        {
            _logConfig.Token = token;
            _logManager.LogConfig = _logConfig;
            var result = _logManager.QueryEventInExceptionless(model, out total);
            return result;
        }

        public BaseResponseModel WriteException(ElpCreateExceptionReqModel model,string token)
        {
            _logConfig.Token = token;
            _logManager.LogConfig = _logConfig;
            var result = _logManager.WriteExceptionToExceptionless(model);
            return result;
        }

        public BaseResponseModel WriteLog(ElpCreateLogReqModel model,string token)
        {
            _logConfig.Token = token;
            _logManager.LogConfig = _logConfig;
            var result = _logManager.WriteLogToExceptionless(model);
            return result;
        }

        /// <summary>
        /// 获取Exceptionless信息从数据库
        /// </summary>
        /// <param name="systemId"></param>
        /// <returns></returns>
        public ResponseModel<Ass_Exceptionless> GetExceptionlessInfo(string systemId)
        {
            ResponseModel<Ass_Exceptionless> result = new ResponseModel<Ass_Exceptionless>() { IsSuccess = false, Msg = string.Empty, Data = new Ass_Exceptionless() };
            result.Data = _exceptionless.Get(i => i.Status == 1 && i.SystemId == systemId);
            if (result.Data == null)
            {
                result.Msg = "未能获取到对应日志系统相关信息";
                return result;
            }
            result.IsSuccess = true;
            return result;
        }

        /// <summary>
        /// 禁用exceptionless信息
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public ResponseModel<Ass_Exceptionless> DisableExceptionless(string id)
        {
            ResponseModel<Ass_Exceptionless> result = new ResponseModel<Ass_Exceptionless>() { IsSuccess = false, Msg = string.Empty, Data = new Ass_Exceptionless() };
            var entity = _exceptionless.Get(i => i.Id == id);
            if (entity == null)
            {
                result.Msg = "未找到对应日志系统信息";
                return result;
            }
            if (entity.Status == 0)
            {
                result.Msg = "日志系统已经被禁用，不能再次禁用";
                return result;
            }
            entity.Status = 0;
            result.IsSuccess = _exceptionless.Update(entity) > 0;
            result.Msg = result.IsSuccess ? "操作成功" : "操作失败";
            result.Data = entity;
            return result;
        }

        /// <summary>
        /// 登录Exceptionless,获取Token
        /// </summary>
        /// <param name="loginModel"></param>
        /// <returns></returns>
        public ResponseModel<TokenModel> Login(EplLoginModel loginModel)
        {
            var result = new ResponseModel<TokenModel>() { IsSuccess = false, Msg = string.Empty };
            _logManager.LogConfig = _logConfig;
            //创建系统
            var loginResult = _logManager.LoginEpl(loginModel);
            if (!loginResult.IsSuccess)
            {
                result.Msg = loginResult.Msg;
                Task.Run(() =>
                {
                    ExceptionlessClient.Default.CreateLog("Brc_PaaS.Bll.Exceptionless.ExceptionlessLog.ProcessToken", $"系统于【{DateTime.Now.ToString("s")}】登录Exceptionless项目失败。失败原因：【{loginResult.Msg}】", LogLevel.Error).Submit();
                });
                return result;
            }
            result.IsSuccess = loginResult.IsSuccess;
            result.Data = loginResult.Data;
            return result;
        }
    }
}
